#pragma once

#include "BoundingBox.h"
#include "BoundingLine.h"
#include "loadTGA.h"
#include "CountdownTimer.h"

#define GRAVITY 250.0f

/**
	* Class for Objects - Hong Tai
	*
	* Sprite storage
	* Rendering of object
	* Gravity fall for object
	* Bounding box and line for object
	* Position + direction of object
	* Width and height of object
*/
class Object{
public:
	enum COLLISIONTYPE { FULLBODY, LEG, HEAD };

private:
	float width, height, counter;
	Vector3D position, direction;
	TextureImage *charTexture;
	int numberOfImages;
	int spriteImageNumber;
	bool haveTexture;

	bool startAnimation;

	float speed, life;

	float r, g, b, a;

	BoundingBox *theBox;
	BoundingLine theLine;

	bool onGround;

	bool hit;

	CCountdownTimer countdownTimer;
	CCountdownTimer hitTimer;
public:
	bool render;
	bool invertImage;
	bool animationFinished;
	bool letOffset;

	Vector3D hOff,oOff;

	Object(void);
	~Object(void);

	/**
		* Function to initialize object
		*
		* @param Initialize position of object
		* @param Initialize width of object
		* @param Initialize height of object
	*/
	void Init(Vector3D position, float width, float height);

	/**
		* Function to initialize line of object if needed
		*
		* @param Initialize start position of line
		* @param Initialize start position of line
	*/
	void InitLine(Vector3D startPos, Vector3D endPos);

	/**
		* Function to set life
		*
		* @param Set life
	*/
	void SetLife(float life);

	virtual void ReduceLife(float damageTaken);

	/**
		* Function to get life
		*
		* @return Get life
	*/
	float GetLife(void);

	void SetSize(float width, float height);

	/**
		* Function to set position of object
		*
		* @param New position to set to
	*/
	void SetPosition(Vector3D position);

	/**
		* Function to change whether player is currently on ground
		*
		* @param True if on ground, false if not
	*/
	void SetOnGround(bool ground);

	/**
		* Function to check whether player is currently on ground
	*/
	bool GetOnGround(void);

	virtual void WallHit(float elapsed);

	/**
		* Function to initialize the how many sprite the object haves
		*
		* @param Number of sprites the object have
	*/
	void InitSprite(int AmountOfSprites);
	
	/**
		* Function to set which sprite image file
		*
		* @param Which number to assign to. Starts from 0
		* @param The image file to link the number to
	*/
	void SetSprite(int spriteNumber, char *imageFile);

	/**
		* Function to change which sprite to show
		*
		* @param Number assigned to sprite to change to
	*/
	void SetSpriteImageNumber(int ImageNumber);

	/**
		* Function to play sprite animation
		*
		* @param First sprite to start animation
		* @param Last sprite for animation
		* @param Interval between changing each sprite
	*/
	void PlaySpriteAnimation(int FirstSprite, int LastSprite, int Interval);

	/**
		* Function to get current image number
	*/
	int GetSpriteImageNumber(void);
	
	/**
		* Function to render object
		*
		* Virtual function. Overload this function if a inherited object needs to render other stuff as well.
	*/
	virtual void RenderObject(void);
	
	/**
		* Function to change the color and opacity of the object
		*
		* @param Red color density
		* @param Green color density
		* @param Blue color density
		* @param Opacity of object
	*/
	void SetColor(float r, float g, float b, float a);

	/**
		* Function to move Object left or right
		*
		* @param Boolean to see which side is he moving. True for left, false for right
		* @param Movement code in here so need elapsed time for frame independent movement
	*/
	virtual void MoveMeLeftRight(bool mode, float elapsed);
	
	/**
		* Function to update the object.
		*
		* If called, will start a gravity fall till stopped.
		* Virtual function. Overload this function if a inherited object needs to update other stuff as well.
		* Create collision check for ground and change it to true to stop it from falling.
		* @param Elapsed time for frame independent movement.
	*/
	virtual bool UpdateObject(Vector3D offset, float elapsedTime);
	
	/**
		* Function to change direction of object
	*/
	void SetDirection(Vector3D direction);

	/**
		* Function to get direction of object
	*/
	Vector3D GetDirection(void);

	/**
		* Function to set speed of object
	*/
	void SetSpeed(float speed);
	
	/**
		* Function to Get speed of object
	*/
	float GetSpeed(void);

	/**
		* Function to get bounding box of object
	*/
	BoundingBox GetBoundingBox(COLLISIONTYPE boxType);
	
	/**
		* Function to get line segment of object
	*/
	BoundingLine GetBoundingLine(void);

	/**
		* Function to get position of object
	*/
	Vector3D GetPosition(void);

	/**
		* Function to get width of object
	*/
	float GetWidth(void);
	
	/**
		* Function to get height of object
	*/
	float GetHeight(void);
};